package com.bdbit.ChargingStation.controller;

import com.alibaba.fastjson.JSONObject;
import com.bdbit.ChargingStation.config.MqttProperties;
import com.bdbit.ChargingStation.controller.rep.WxpayNotifyBody;
import com.bdbit.ChargingStation.controller.resp.RespObj;
import com.bdbit.ChargingStation.dao.impl.order_impl;
import com.bdbit.ChargingStation.entity.*;

import static com.bdbit.ChargingStation.entity.ChargingOrder.STATUS_UNPAID;
import static java.lang.Thread.sleep;

import com.bdbit.ChargingStation.mapper.ChargingPileMapper;
import com.bdbit.ChargingStation.services.*;
import com.bdbit.ChargingStation.wx.AesUtil;
import com.bdbit.ChargingStation.wx.WxConfig;
import com.bdbit.ChargingStation.wx.results.NotifyResource;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.gson.JsonSyntaxException;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.context.annotation.Lazy;
import org.springframework.format.annotation.DateTimeFormat;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.math.BigDecimal;
import java.nio.charset.StandardCharsets;
import java.security.GeneralSecurityException;
import java.security.PublicKey;
import java.security.Signature;
import java.text.SimpleDateFormat;
import java.time.LocalDate;
import java.util.*;
import java.util.stream.Collectors;
import java.util.Map;

@Slf4j
@RestController
@EnableAutoConfiguration
@RequestMapping("/api/order")
/**
 * 订单控制器+获取充电桩信息12121
 * 包含了订单管理、充电桩信息获取、微信支付、支付宝支付、订单查询、订单完成、订单取消、订单退款、订单支付状态查询、订单支付状态修改、订单支付状态查询、订单支付状态修改、订单支付状态查询、订单支付状态修改、订单支付状态查询、订单支付状态修改、订单支付状态查询、订单支付状态修改、订单支付状态查询、订单支付状态修改、订单支付状态查询、订单支付
 * 订单管理
 */
public class ChargingOrderController {

    // 微信支付相关
    private final Gson gson = new GsonBuilder().serializeNulls().create();
    @Autowired
    private ChargingPileMapper chargingPileMapper;
    @Autowired
    JdbcTemplate jct;
    @Autowired
    private AliPayService aliPayService;
    @Autowired
    private WXPayService wxpayService;
    @Autowired
    private WxService wxService;
    @Autowired
    private OrderService orderService;
    @Autowired
    @Lazy
    private MqttServerService mqttServerService;
    @Autowired
    private ChargingOrderService chargingOrderService;
    @Autowired
    private MqttProperties mqttProperties;
    @Autowired
    private PaymentService paymentService;
    @Autowired
    private SimpleChargingRetryService simpleChargingRetryService;
    @Autowired
    private DeviceOrderService deviceOrderService;

    public ChargingOrderController(JdbcTemplate jct) {
        this.jct = jct;
    }

    // 微信支付接口TODO 待完善123
    @PostMapping("/wxPayPrepay")
    public RespObj<String> wxPayPrepay(@RequestBody Map<String, Object> requestMap) {
        bean_order param = new bean_order();
        
        // 手动处理字段映射，支持两种格式
        if (requestMap.containsKey("prepay_amount")) {
            param.setPrepayAmount(new BigDecimal(requestMap.get("prepay_amount").toString()));
        } else if (requestMap.containsKey("prepayAmount")) {
            param.setPrepayAmount(new BigDecimal(requestMap.get("prepayAmount").toString()));
        }
        
        if (requestMap.containsKey("open_id")) {
            param.setUserId(requestMap.get("open_id").toString());
        }
        
        if (requestMap.containsKey("region_code")) {
            param.setRegionCode(requestMap.get("region_code").toString());
        }
        
        if (requestMap.containsKey("ele_code")) {
            param.setEleCode(requestMap.get("ele_code").toString());
        }
        
        // 添加详细参数日志
        log.info("收到支付请求 - 详细参数: ele_code={}, open_id={}, prepayAmount={}, region_code={}",
                param.getEleCode(), param.getUserId(), param.getPrepayAmount(), param.getRegionCode());

        // 修复对象属性的日志打印问题
        log.info("收到支付请求对象: {}", param);
        RespObj<String> resp = new RespObj<>();

        try {
            // 添加参数验证
            if (param.getPrepayAmount() == null || param.getPrepayAmount().compareTo(new BigDecimal("0.01")) < 0) {
                log.error("支付金额无效: prepayAmount={}", param.getPrepayAmount());
                resp.setCode(400);
                resp.setMessage("支付金额不能为空且不能小于0.01元");
                return resp;
            }
            // --- 订单号和日期修复 ---
            // 1. 生成一个唯一的订单号。使用时间戳+UUID确保唯一且长度足够。
            String uniqueOrderId = "ORDER" + System.currentTimeMillis() + UUID.randomUUID().toString().substring(0, 5);
            param.setOrderId(uniqueOrderId);
            SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM");
            param.setOrderYearMonth(sdf.format(new Date()));
            // 2. 在这里设置创建和更新时间，确保 insertOrder 接收到非空值
            // 2. 设置订单状态为"未支付"(0)
            param.setStatus(0); // 0表示未支付
            Date now = new Date();
            param.setCreateDate(now);
            param.setUpdateDate(now);

            // --- 修复结束 ---

            order_impl orderDao = new order_impl(jct);
            int result = orderDao.insertOrder(param);

            if (result != 1) {
                log.error("订单创建失败，参数: {}", param);
                resp.setCode(0);
                resp.setMessage("订单创建失败");
                return resp;
            }

            // 前端传递的prepayAmount已经是元为单位，直接使用
            BigDecimal totalMoneyInYuan = param.getPrepayAmount();
            log.info("充电桩订单创建成功: 订单ID={}, 金额={}元", 
                    param.getOrderId(), totalMoneyInYuan);

            // 生成支付表单 - 直接传递元为单位
            String paymentForm = wxpayService.wxPayJsapi(
                    param.getUserId(),      // 用户的 openid
                    param.getOrderId(),     // 确保订单号已设置
                    totalMoneyInYuan.toString()  // 传递元为单位
            );

            // 更新订单支付方式和支付表单
            String updateSql = "UPDATE charging_order SET pay_type = ?, payment_form = ? WHERE order_id = ?";
            jct.update(updateSql, "wxpay", paymentForm, param.getOrderId());

            resp.setCode(200);
            resp.setData(paymentForm);

        } catch (Exception e) {
            log.error("处理支付请求失败", e);
            resp.setCode(500);
            resp.setMessage("系统错误");
        }
        return resp;
    }

    @GetMapping("/getwxopenid")
    public String getWxOpenid(@RequestParam String code) {
        try {
            String openid = wxService.getAccessToken(code);
            if (openid != null){
                return openid;
            }
            return "获取openid失败";
        } catch (IOException e) {
            throw new RuntimeException(e);
        }

    }
    
    @GetMapping("/getalipayuserid")
    public String getAlipayUserId(@RequestParam String auth_code) {
        try {
            // 参数验证和日志
            log.info("收到获取支付宝用户ID请求，授权码: {}", auth_code);
            
            if (auth_code == null || auth_code.trim().isEmpty()) {
                log.error("授权码参数为空");
                return "授权码不能为空";
            }
            
            String userId = aliPayService.getUserId(auth_code);
            if (userId != null && !userId.trim().isEmpty()) {
                log.info("成功获取支付宝用户ID: {}", userId);
                return userId;
            } else {
                log.error("获取支付宝用户ID失败，返回null或空字符串");
                return "获取用户ID失败，请检查授权码是否有效";
            }
        } catch (Exception e) {
            log.error("获取支付宝用户ID异常", e);
            return "系统异常：" + e.getMessage();
        }
    }
    // 支付宝支付接口TODO 待完善212
    @PostMapping("/alipayCreateOrder")
    public RespObj<String> alipayCreateOrder(@RequestBody bean_order param) {
        
        // 添加详细参数日志
        log.info("收到支付宝支付请求 - 详细参数: ele_code={}, user_id={}, prepayAmount={}, region_code={}",
                param.getEleCode(), param.getUserId(), param.getPrepayAmount(), param.getRegionCode());
        
        log.info("收到支付宝支付请求对象: {}", param);
        RespObj<String> resp = new RespObj<>();
        
        try {
            // 添加参数验证
            if (param.getPrepayAmount() == null || param.getPrepayAmount().compareTo(new BigDecimal("0.01")) < 0) {
                log.error("支付金额无效: prepayAmount={}", param.getPrepayAmount());
                resp.setCode(400);
                resp.setMessage("支付金额不能为空且不能小于0.01元");
                return resp;
            }
            // 生成唯一订单号
            String uniqueOrderId = "ORDER" + System.currentTimeMillis() + UUID.randomUUID().toString().substring(0, 5);
            param.setOrderId(uniqueOrderId);
            SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM");
            param.setOrderYearMonth(sdf.format(new Date()));
            
            // 设置订单状态为"未支付"(0)
            param.setStatus(0);
            Date now = new Date();
            param.setCreateDate(now);
            param.setUpdateDate(now);
            
            // 创建订单
            order_impl orderDao = new order_impl(jct);
            int result = orderDao.insertOrder(param);
            
            if (result != 1) {
                log.error("订单创建失败，参数: {}", param);
                resp.setCode(0);
                resp.setMessage("订单创建失败");
                return resp;
            }
            
            // 前端传递的prepayAmount已经是元为单位，直接使用
            BigDecimal totalMoneyInYuan = param.getPrepayAmount();
            log.info("支付宝订单创建成功: 订单ID={}, 金额={}元", 
                    param.getOrderId(), totalMoneyInYuan);
            
            // 生成支付表单 - 只传递订单号和金额
            String paymentForm = aliPayService.aliWappay(
                    param.getOrderId(),     // 订单号
                    totalMoneyInYuan.toString()  // 金额（元为单位）
            );
            
            // 更新订单支付方式和支付表单
            String updateSql = "UPDATE charging_order SET pay_type = ?, payment_form = ? WHERE order_id = ?";
            jct.update(updateSql, "alipay", paymentForm, param.getOrderId());
            
            resp.setCode(200);
            resp.setData(paymentForm);
            
        } catch (Exception e) {
            log.error("处理支付宝支付请求失败", e);
            resp.setCode(500);
            resp.setMessage("系统错误");
        }
        return resp;
    }



    /**
     * 支付宝充电支付异步通知
     * TODO 待完善
     */
    @PostMapping(value = "/alipayNotify", consumes = "application/x-www-form-urlencoded")
    public String handleAlipayNotify(@RequestParam Map<String, String> paramsMap) {
        try {
            // 1. 记录回调参数（用于调试）
            log.info("收到支付宝回调通知: {}", paramsMap);
            
            // 2. 验证签名
            boolean signVerified = aliPayService.verifySignature(paramsMap);
            if (!signVerified) {
                log.error("支付宝回调签名验证失败: {}", paramsMap);
                return "failure";
            }
            log.info("支付宝回调签名验证成功");
            
            // 3. 获取关键参数
            String outTradeNo = paramsMap.get("out_trade_no");
            String tradeStatus = paramsMap.get("trade_status");
            String totalAmount = paramsMap.get("total_amount");
            String tradeNo = paramsMap.get("trade_no"); // 支付宝交易号
            
            log.info("支付宝回调解析: 订单号={}, 状态={}, 金额={}, 支付宝交易号={}", 
                    outTradeNo, tradeStatus, totalAmount, tradeNo);
            
            // 4. 检查幂等性
            if (isPaymentAlreadyProcessed(outTradeNo)) {
                log.info("订单已处理过，跳过: {}", outTradeNo);
                return "success";
            }
            
            // 5. 处理支付成功
            if ("TRADE_SUCCESS".equals(tradeStatus) || "TRADE_FINISHED".equals(tradeStatus)) {
                log.info("开始处理支付成功逻辑: 订单号={}", outTradeNo);
                handleSuccessfulPayment(outTradeNo);
                log.info("支付成功处理完成: 订单号={}", outTradeNo);
            } else {
                log.warn("支付状态不是成功状态: 订单号={}, 状态={}", outTradeNo, tradeStatus);
            }
            
            return "success";
        } catch (Exception e) {
            log.error("处理支付宝回调异常: {}", paramsMap, e);
            return "failure";
        }
    }

    /**
     * 微信支付回调TODO 待完善
     *
     * @param
     * @throws GeneralSecurityException
     * @throws IOException
     */

    @PostMapping("/wxpayNotify")
    public void wxpayNotify(HttpServletRequest request, HttpServletResponse response)
            throws IOException, GeneralSecurityException {

        // 1. 记录请求头信息（用于调试）
        logHeaders(request);

        // 2. 读取原始请求体
        String requestBody = request.getReader().lines().collect(Collectors.joining());
        log.info("收到微信支付回调原始数据: {}", requestBody);

        try {
            // 3. 验证签名
            if (!verifySignature(request, requestBody)) {
                log.error("签名验证失败");
                sendFailResponse(response, "SIGNATURE_INVALID");
                return;
            }

            // 4. 解析JSON
            WxpayNotifyBody body = gson.fromJson(requestBody, WxpayNotifyBody.class);
            log.info("解析后的回调对象: {}", gson.toJson(body));

            // 5. 解密回调报文
            AesUtil aesUtil = new AesUtil(WxConfig.apiV3key.getBytes());
            WxpayNotifyBody.Resource resource = body.getResource();
            String data = aesUtil.decryptToString(
                    resource.getAssociated_data().getBytes(),
                    resource.getNonce().getBytes(),
                    resource.getCiphertext()
            );

            log.info("解密后的回调数据: {}", data);

            // 6. 解析解密后的数据
            NotifyResource notifyResource = gson.fromJson(data, NotifyResource.class);
            String orderNo = notifyResource.getOutTradeNo();
            String tradeState = notifyResource.getTradeState();

            log.info("支付回调解析: 订单ID={}, 状态={}", orderNo, tradeState);

            if ("SUCCESS".equals(tradeState)) {
                // 7. 处理支付成功逻辑
                handleSuccessfulPayment(orderNo);
            }

            // 8. 返回成功响应
            sendSuccessResponse(response);

        } catch (JsonSyntaxException e) {
            log.error("JSON解析失败", e);
            sendFailResponse(response, "JSON_PARSE_ERROR");
        } catch (GeneralSecurityException e) {
            log.error("解密失败", e);
            sendFailResponse(response, "DECRYPT_FAILED");
        } catch (Exception e) {
            log.error("处理回调异常", e);
            response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
        }
    }

    // 记录请求头信息
    private void logHeaders(HttpServletRequest request) {
        Enumeration<String> headerNames = request.getHeaderNames();
        while (headerNames.hasMoreElements()) {
            String name = headerNames.nextElement();
            log.info("Header: {} = {}", name, request.getHeader(name));
        }
    }

    // 验证签名
    private boolean verifySignature(HttpServletRequest request, String requestBody) {
        try {
            String signature = request.getHeader("Wechatpay-Signature");
            String timestamp = request.getHeader("Wechatpay-Timestamp");
            String nonce = request.getHeader("Wechatpay-Nonce");
            String serialNo = request.getHeader("Wechatpay-Serial");

            // 构建验签字符串
            String message = timestamp + "\n" + nonce + "\n" + requestBody + "\n";

            // 获取公钥
            PublicKey publicKey = wxService.getPublicKeyBySerial(serialNo);
            if (publicKey == null) {
                // 尝试刷新证书
                try {
                    wxService.refreshWechatCertificates();
                    publicKey = wxService.getPublicKeyBySerial(serialNo);
                } catch (Exception e) {
                    log.error("刷新证书失败", e);
                }

                if (publicKey == null) {
                    log.error("无法获取证书序列号对应的公钥: {}", serialNo);
                    return false;
                }
            }

            // 验证签名
            return verifySignatureWithPublicKey(publicKey, message, signature);
        } catch (Exception e) {
            log.error("签名验证异常", e);
            return false;
        }
    }

    // 新增辅助方法
    private boolean verifySignatureWithPublicKey(PublicKey publicKey, String message, String signature) {
        try {
            Signature signer = Signature.getInstance("SHA256withRSA");
            signer.initVerify(publicKey);
            signer.update(message.getBytes(StandardCharsets.UTF_8));
            return signer.verify(Base64.getDecoder().decode(signature));
        } catch (Exception e) {
            log.error("签名验证失败", e);
            return false;
        }
    }
    // 处理支付成功逻辑
    public void handleSuccessfulPayment(String orderNo) {
        try {
            log.info("开始处理支付成功，订单号: {}", orderNo);
            
            OrderEntity order = orderService.getOrderByOrderNo(orderNo);
            if (order != null) {
                log.info("找到订单，当前状态: {}, ID: {}", order.getStatus(), order.getId());
                
                // 更新订单状态为已支付
                order.setPaymentTime(new Date()); // 设置支付时间
                order.setStatus(1); // 1-已支付，准备充电
                order.setUpdateDate(new java.sql.Date(System.currentTimeMillis()));
                
                // 新增：根据支付金额计算充电时长（1元=5分钟）
                if (order.getPrepayAmount() != null) {
                    int chargingMinutes = (int) (order.getPrepayAmount().doubleValue() * 5);
                    order.setChargingMinutes(chargingMinutes);
                    log.info("根据支付金额计算充电时长: 支付金额={}元, 充电时长={}分钟",
                            order.getPrepayAmount(), chargingMinutes);
                }
                
                log.info("准备更新订单状态，订单ID: {}, 新状态: {}", order.getId(), order.getStatus());
                
                // 执行数据库更新
                orderService.updateOrder(order);
                
                log.info("订单状态更新成功，订单号: {}", orderNo);
                
                // 发送支付成功通知
                try {
                    sendPaymentSuccessNotification(order);
                    log.info("支付成功通知发送完成");
                } catch (Exception e) {
                    log.error("发送支付成功通知失败", e);
                }
                
                // 发送充电启动指令
                try {
                    sendStartChargingCommand(order);
                    log.info("充电启动指令发送完成");
                } catch (Exception e) {
                    log.error("发送充电启动指令失败", e);
                }
                
                // 发送短信通知
                try {
                    sendPaymentSuccessSms(order);
                    log.info("短信通知发送完成");
                } catch (Exception e) {
                    log.error("发送短信通知失败", e);
                }
                
                log.info("支付成功处理完成: 订单号={}", orderNo);
            } else {
                log.error("订单不存在: ID={}", orderNo);
            }
        } catch (Exception e) {
            log.error("处理支付成功逻辑时发生异常: 订单号={}", orderNo, e);
            throw e; // 重新抛出异常，让上层处理
        }
    }

    /**
     * 检查支付是否已经处理过（幂等性检查）
     */
    private boolean isPaymentAlreadyProcessed(String orderNo) {
        try {
            OrderEntity order = orderService.getOrderByOrderNo(orderNo);
            return order != null && order.getStatus() != null && order.getStatus() > 0;
        } catch (Exception e) {
            log.error("检查订单状态失败: orderNo={}", orderNo, e);
            return false;
        }
    }

    // 返回成功响应
    private void sendSuccessResponse(HttpServletResponse response) throws IOException {
        response.setContentType("application/json");
        response.getWriter().write("{\"code\": \"SUCCESS\", \"message\": \"成功\"}");
    }

    // 返回失败响应
    private void sendFailResponse(HttpServletResponse response, String errorCode) throws IOException {
        response.setContentType("application/json");
        response.setStatus(HttpServletResponse.SC_OK);
        response.getWriter().write(String.format(
                "{\"code\": \"FAIL\", \"message\": \"%s\"}",
                errorCode
        ));
    }

//    private void handlePaymentSuccess(OrderEntity order) {
//
//        order.setStatus(1);
//        orderService.updateOrder(order);
//        sendPaymentSuccessNotification(order);
//        sendStartChargingCommand(order);
//        sendPaymentSuccessSms(order);
//    }

    // 新增：获取充电桩信息接口
    @GetMapping("/getChargingPiles")
    public ChargingPileController.ApiResponse getChargingPiles(
            @RequestParam(value = "region_code", required = false) String regionCode,
            @RequestParam(value = "ele_code", required = false) String eleCode) {

        try {
            List<ChargingPile> resultList;

            // 模式0: 无任何参数时返回全部
            if (StringUtils.isEmpty(regionCode) && StringUtils.isEmpty(eleCode)) {
                resultList = chargingPileMapper.selectAll();
            }
            // 模式1: 只提供区域编码
            else if (!StringUtils.isEmpty(regionCode) && StringUtils.isEmpty(eleCode)) {
                resultList = chargingPileMapper.selectByRegion(regionCode);
            }
            // 模式2: 只提供电桩号
            else if (StringUtils.isEmpty(regionCode) && !StringUtils.isEmpty(eleCode)) {
                resultList = chargingPileMapper.selectByEleCode(eleCode);
            }
            // 模式3: 提供区域+电桩号
            else {
                ChargingPile pile = chargingPileMapper.selectByRegionAndCode(regionCode, eleCode);
                resultList = pile != null ? Collections.singletonList(pile) : Collections.emptyList();
            }

            return ChargingPileController.ApiResponse.success(resultList);
        } catch (Exception e) {
            return ChargingPileController.ApiResponse.error(500, "查询失败: " + e.getMessage());
        }
    }

    /**
     * 获取所有充电桩信息
     *
     * @return
     */
    @GetMapping("/getAllChargingPiles")
    public ChargingPileController.ApiResponse getAllChargingPiles() {
        try {
            List<ChargingPile> allPiles = chargingPileMapper.selectAll();
            return ChargingPileController.ApiResponse.success(allPiles);
        } catch (Exception e) {
            return ChargingPileController.ApiResponse.error(500, "获取所有充电桩信息失败: " + e.getMessage());
        }
    }

    /**
     * 获取某一个电桩下全部订单，倒序排列
     *
     * @return
     */
    @GetMapping("/getChargingPilesOrder")
    public ChargingPileController.ApiResponse getChargingPilesOrder(@RequestParam String eleCode) {
        try {
            List<OrderEntity> allPiles = chargingPileMapper.getChargingPilesOrder(eleCode);
            return ChargingPileController.ApiResponse.success_order(allPiles);
        } catch (Exception e) {
            return ChargingPileController.ApiResponse.error(500, "获取此充电桩订单信息失败: " + e.getMessage());
        }
    }

    // 充电桩订单相关接口
    @PostMapping("/createOrder")
    public returnBean<ChargingOrder> createOrder(@RequestBody ChargingOrder order) {
        try {
            // 验证必要字段
            if (order.getUserId() == null || order.getUserId().isEmpty()) {
                return returnBean.error(400, "用户ID不能为空");
            }
            if (order.getEleCode() == null || order.getEleCode().isEmpty()) {
                return returnBean.error(400, "电桩号不能为空");
            }
            if (order.getRegionCode() == null || order.getRegionCode().isEmpty()) {
                return returnBean.error(400, "区域编码不能为空");
            }

            // 设置默认值
            order.setStatus(STATUS_UNPAID);
            order.setCreateDate(new Date());
            order.setUpdateDate(new Date());
            order.setIsDeleted(0);

            // 设置 orderYearMonth
            SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM");
            order.setOrderYearMonth(sdf.format(new Date()));

            // 确保预付金额不为空
            if (order.getPrepayAmount() == null) {
                order.setPrepayAmount(BigDecimal.ZERO);
            }

            // 计算总金额
            if (order.getChargingKwh() != null && order.getUnitPrice() != null) {
                BigDecimal total = order.getChargingKwh().multiply(order.getUnitPrice());
                order.setTotalAmount(total);
            } else {
                order.setTotalAmount(BigDecimal.ZERO);
            }

            // 清除时间字段
            order.setStartTime(null);
            order.setEndTime(null);
            order.setDeviceStartTime(null);
            order.setDeviceEndTime(null);
            order.setPaymentTime(null);
            order.setRefundTime(null);

            ChargingOrder createdOrder = chargingOrderService.createOrder(order);
            return returnBean.success(createdOrder);
        } catch (Exception e) {
            log.error("创建订单失败", e);
            return returnBean.error(500, "系统错误: " + e.getMessage());
        }
    }

    /**
     * 更新订单信息
     *
     * @param id    订单ID
     * @param order 包含更新信息的订单对象
     * @return 更新后的订单信息
     */
    @PutMapping("/updateOrder/{id}")
    public returnBean<ChargingOrder> updateOrder(@PathVariable Long id, @RequestBody ChargingOrder order) {
        order.setId(id);
        ChargingOrder updatedOrder = chargingOrderService.updateOrder(order);
        return returnBean.success(updatedOrder);
    }


    /**
     * 删除订单
     *
     * @param id 要删除的订单ID
     * @return 操作结果
     */
    @DeleteMapping("/deleteOrder/{id}")
    public returnBean<Void> deleteOrder(@PathVariable Long id) {
        chargingOrderService.deleteOrder(id);
        return returnBean.success(null);
    }

    /**
     * 根据ID获取订单详情
     *
     * @param id 订单ID
     * @return 订单信息
     */
    @GetMapping("/getOrderById/{id}")
    public returnBean<ChargingOrder> getOrderById(@PathVariable Long id) {
        ChargingOrder order = chargingOrderService.getOrderById(id);
        return returnBean.success(order);
    }

    /**
     * 更新订单状态
     *
     * @param orderId 订单ID
     * @param status  新的订单状态
     * @return 更新后的订单信息
     */
    @PutMapping("/status/update")
    public returnBean<OrderEntity> updateOrderStatus(@RequestParam String orderId, @RequestParam Integer status) {
        // 实现更新订单状态逻辑
        try {
            // 先检查订单是否存在
            String selectSql = "SELECT * FROM orders WHERE order_id = ?";
            OrderEntity order = jct.queryForObject(selectSql, OrderEntity.class, orderId);

            // 验证状态值是否有效
            if (status != ChargingOrder.STATUS_UNPAID &&
                    status != ChargingOrder.STATUS_PAID_WAITING &&
                    status != ChargingOrder.STATUS_CHARGING &&
                    status != ChargingOrder.STATUS_COMPLETED &&
                    status != ChargingOrder.STATUS_REFUNDED &&
                    status != ChargingOrder.STATUS_TIMEOUT &&
                    status != ChargingOrder.STATUS_CANCELLED) {
                return returnBean.error(400, "无效的订单状态");
            }

            // 更新状态
            order.setStatus(status);

            // 执行更新
            String sql = "UPDATE orders SET status = ? WHERE order_id = ?";
            jct.update(sql, status, orderId);

            return returnBean.success(order);
        } catch (Exception e) {
            String errorMessage = "订单状态更新失败: " + e.getMessage().replace("\\", "\\\\").replace("'", "\\'");
            return returnBean.error(500, errorMessage);
        }
    }

    /**
     * 更新订单状态（通过服务层）
     *
     * @param orderId 订单ID
     * @param status  新的订单状态
     * @return 更新后的订单信息
     */
    @PutMapping("/status/updateorderstatus2")
    public returnBean<OrderEntity> updateOrderStatus2(@RequestParam String orderId,
                                                      @RequestParam Integer status) {
        try {
            OrderEntity updatedOrder2 = chargingOrderService.updateOrderStatus2(orderId, status);
            return returnBean.success(updatedOrder2);
        } catch (IllegalArgumentException e) {
            // 业务校验错误（400）
            return returnBean.error(400, e.getMessage());
        } catch (Exception e) {
            // 系统错误（500）
            return returnBean.error(500, "订单状态更新失败: " +
                    e.getMessage().replace("\\", "\\\\").replace("'", "\\'"));
        }
    }

    /**
     * 根据订单ID获取订单状态
     *
     * @param id 订单ID
     * @return 订单状态
     */
    @GetMapping("/getOrderStatus/{id}")
    public returnBean<Integer> getOrderStatus(@PathVariable Long id) {
        try {
            Integer status = chargingOrderService.getOrderstatusbyid(id);
            if (status != null) {
                return returnBean.success(status);
            } else {
                return returnBean.error(404, "订单不存在");
            }
        } catch (Exception e) {
            log.error("获取订单状态失败", e);
            String errorMessage = "系统错误: " + e.getMessage().replace("\\", "\\\\");
            return returnBean.error(500, errorMessage);
        }
    }

    /**
     * 获取订单充电状态
     *
     * @param id 订单ID
     * @return 包含充电状态的响应对象
     */
    @GetMapping("/chargingStatus/{id}")
    public returnBean<Integer> getChargingStatus(@PathVariable Long id) {
        try {
            Integer status = chargingOrderService.getOrderstatusbyid(id);
            if (status != null) {
                // 将订单状态映射为充电状态
                int chargingStatus = mapOrderStatusToChargingStatus(status);
                return returnBean.success(chargingStatus);
            } else {
                return returnBean.error(404, "订单不存在");
            }
        } catch (Exception e) {
            log.error("获取充电状态失败", e);
            return returnBean.error(500, "系统错误: " + e.getMessage());
        }
    }

    /**
     * 将订单状态映射为充电状态
     *
     * @param orderStatus 订单状态
     * @return 充电状态
     */
    private int mapOrderStatusToChargingStatus(int orderStatus) {
        switch (orderStatus) {
            case ChargingOrder.STATUS_UNPAID:
                return 0; // 未支付状态对应充电未开始
            case ChargingOrder.STATUS_PAID_WAITING:
                return 0; // 已支付待充电状态对应充电未开始
            case ChargingOrder.STATUS_CHARGING:
                return 1; // 充电中状态对应充电中
            case ChargingOrder.STATUS_COMPLETED:
                return 2; // 已完成状态对应充电完成
            case ChargingOrder.STATUS_REFUNDED:
                return 3; // 已退款状态对应充电异常中断
            case ChargingOrder.STATUS_TIMEOUT:
                return 3; // 超时状态对应充电异常中断
            case ChargingOrder.STATUS_CANCELLED:
                return 3; // 已取消状态对应充电异常中断
            default:
                return -1; // 未知状态
        }
    }

    /**
     * 获取所有订单列表
     *
     * @param startDate 查询起始日期（可选）
     * @param endDate   查询结束日期（可选）
     * @return 订单列表
     */
    @GetMapping("/getAllOrders")
    public returnBean<List<ChargingOrder>> getAllOrders(
            @RequestParam(required = false) @DateTimeFormat(iso = DateTimeFormat.ISO.DATE) LocalDate startDate,
            @RequestParam(required = false) @DateTimeFormat(iso = DateTimeFormat.ISO.DATE) LocalDate endDate) {

        try {
            // 日期范围验证
            if (startDate != null && endDate != null && startDate.isAfter(endDate)) {
                return returnBean.error(400, "开始日期不能晚于结束日期");
            }

            List<ChargingOrder> orders = chargingOrderService.getAllOrders(
                    (startDate != null) ? startDate.toString() : null,
                    (endDate != null) ? endDate.toString() : null);

            return returnBean.success(orders);
        } catch (Exception e) {
            log.error("获取所有订单异常", e);
            return returnBean.error(500, "获取所有订单失败: " + e.getMessage());
        }
    }

    /**
     * 根据用户ID获取订单列表
     *
     * @param userId    用户ID
     * @param startDate 查询起始日期（可选）
     * @param endDate   查询结束日期（可选）
     * @return 用户的订单列表
     */
    @GetMapping("/getOrdersByUser/{userId}")
    public returnBean<List<ChargingOrder>> getOrdersByUser(
            @PathVariable String userId,
            @RequestParam(required = false) @DateTimeFormat(iso = DateTimeFormat.ISO.DATE) LocalDate startDate,
            @RequestParam(required = false) @DateTimeFormat(iso = DateTimeFormat.ISO.DATE) LocalDate endDate) {

        try {
            // 日期范围验证
            if (startDate != null && endDate != null && startDate.isAfter(endDate)) {
                return returnBean.error(400, "开始日期不能晚于结束日期");
            }

            List<ChargingOrder> orders = chargingOrderService.getOrdersByUser(
                    userId,
                    (startDate != null) ? startDate.toString() : null,
                    (endDate != null) ? endDate.toString() : null);

            return returnBean.success(orders);
        } catch (Exception e) {
            log.error("获取用户订单异常", e);
            return returnBean.error(500, "获取用户订单失败: " + e.getMessage());
        }
    }

    /**
     * 根据订单状态获取订单列表
     *
     * @param status    订单状态
     * @param startDate 查询起始日期（可选）
     * @param endDate   查询结束日期（可选）
     * @return 指定状态的订单列表
     */
    @GetMapping("/getOrdersByStatus/{status}")
    public returnBean<List<ChargingOrder>> getOrdersByStatus(
            @PathVariable Integer status,
            @RequestParam(required = false) @DateTimeFormat(iso = DateTimeFormat.ISO.DATE) LocalDate startDate,
            @RequestParam(required = false) @DateTimeFormat(iso = DateTimeFormat.ISO.DATE) LocalDate endDate) {

        try {
            // 日期范围验证
            if (startDate != null && endDate != null && startDate.isAfter(endDate)) {
                return returnBean.error(400, "开始日期不能晚于结束日期");
            }

            List<ChargingOrder> orders = chargingOrderService.getOrdersByStatus(
                    status,
                    (startDate != null) ? startDate.toString() : null,
                    (endDate != null) ? endDate.toString() : null);

            return returnBean.success(orders);
        } catch (Exception e) {
            log.error("按状态获取订单异常", e);
            return returnBean.error(500, "按状态获取订单失败: " + e.getMessage());
        }
    }

    /**
     * 开始充电
     *
     * @param id 订单ID
     * @return 更新后的订单信息
     */
    @PostMapping("/startCharging/{id}/start")
    public returnBean<ChargingOrder> startCharging(@PathVariable Long id) {
        ChargingOrder order = chargingOrderService.startCharging(id);
        return returnBean.success(order);
    }

    /**
     * 停止充电
     *
     * @param id 订单ID
     * @return 更新后的订单信息
     */
    @PostMapping("/stopCharging/{id}/stop")
    public returnBean<ChargingOrder> stopCharging(@PathVariable Long id) {
        ChargingOrder order = chargingOrderService.stopCharging(id);
        return returnBean.success(order);
    }

    /**
     * 处理退款
     * TODO 待完善
     *
     * @param id 订单ID
     * @return 更新后的订单信息
     */
    @PostMapping("/processRefund/{id}/refund")
    public returnBean<ChargingOrder> processRefund(@PathVariable Long id) {
        ChargingOrder order = chargingOrderService.processRefund(id);
        return returnBean.success(order);
    }

    /**
     * 获取所有处于活动状态的充电订单
     * <p>
     * 该方法通过发送GET请求到"/getActiveOrders/active"来调用，
     * 它将返回一个包含活动充电订单列表的ReturnBean对象
     *
     * @return ReturnBean 包含活动充电订单列表的ReturnBean对象
     */
    @GetMapping("/getActiveOrders/active")
    public returnBean<List<ChargingOrder>> getActiveOrders() {
        List<ChargingOrder> orders = chargingOrderService.getActiveOrders();
        return returnBean.success(orders);
    }

    /**
     * 搜索订单
     *
     * @param userId     用户ID（可选）
     * @param status     订单状态（可选）
     * @param regionCode 区域编码（可选）
     * @param eleCode    电桩编号（可选）
     * @param startDate  查询起始日期（可选）
     * @param endDate    查询结束日期（可选）
     * @param page       页码，默认为0
     * @param size       每页大小，默认为10
     * @return 分页查询结果
     */
    @GetMapping("/searchOrders/search")
    public returnBean<PageResult<ChargingOrder>> searchOrders(
            @RequestParam(required = false) String userId,
            @RequestParam(required = false) Integer status,
            @RequestParam(required = false) String regionCode,
            @RequestParam(required = false) String eleCode,
            @RequestParam(required = false) @DateTimeFormat(iso = DateTimeFormat.ISO.DATE) LocalDate startDate,
            @RequestParam(required = false) @DateTimeFormat(iso = DateTimeFormat.ISO.DATE) LocalDate endDate,
            @RequestParam(defaultValue = "0") int page,
            @RequestParam(defaultValue = "10") int size) {

        try {
            // 日期范围验证
            if (startDate != null && endDate != null && startDate.isAfter(endDate)) {
                return returnBean.error(400, "开始日期不能晚于结束日期");
            }

            PageResult<ChargingOrder> result = chargingOrderService.searchOrders(
                    userId, status, regionCode, eleCode,
                    (startDate != null) ? startDate.toString() : null,
                    (endDate != null) ? endDate.toString() : null,
                    page, size
            );

            // 添加日志输出，方便调试
            log.info("搜索结果: {} 条记录", result.getContent().size());
            log.info("查询参数: userId={}, status={}, regionCode={}, eleCode={}, startDate={}, endDate={}",
                    userId, status, regionCode, eleCode, startDate, endDate);

            return returnBean.success(result);
        } catch (Exception e) {
            log.error("订单搜索异常", e);
            return returnBean.error(500, "查询失败: " + e.getMessage());
        }
    }

    /**
     * 发送支付成功通知
     * TODO 待完善
     *
     * @param order 订单信息
     */
    private void sendPaymentSuccessNotification(OrderEntity order) {
        try {
            JSONObject mqttMsg = new JSONObject();
            mqttMsg.put("event_type", "charging_payment_success");
            mqttMsg.put("order_id", order.getOrderId());
            mqttMsg.put("pile_id", order.getPileId());
            mqttMsg.put("ele_code", order.getEleCode());
            mqttMsg.put("amount", order.getPrepayAmount());
            mqttMsg.put("user_id", order.getUserId());

            if (order.getUserId() != null && order.getUserId().length() >= 4) {
                String clientSuffix = order.getUserId().substring(order.getUserId().length() - 4);
                String topic = "notify/charging/" + clientSuffix;
                mqttServerService.sendToDevice(topic, mqttMsg.toJSONString());
                log.info("支付成功通知已发送: {}", topic);
            } else {
                mqttServerService.sendToDevice("notify/charging/default", mqttMsg.toJSONString());
            }
        } catch (Exception e) {
            log.error("发送支付成功通知失败", e);
        }
    }

    /**
     * 发送充电启动指令
     *
     * @param order 订单信息
     */
    public void sendStartChargingCommand(OrderEntity order) {
        try {
            // 使用新方法获取真实的IMEI121
            String imei = getDeviceRealImei(order.getEleCode());
            if (imei == null) {
                log.error("无法获取充电桩IMEI: eleCode={}", order.getEleCode());
                return;
            }

            // 模式2格式：IMEI.时长参数.00
            // 按照新的计费标准：1元=5分钟
            int chargingMinutes = order.getChargingMinutes() != null ? order.getChargingMinutes() : 5; // 默认改为5分钟
            
            // 将分钟转换为充电桩能理解的时长参数（乘以10的小时数
            //double hours = chargingMinutes / 60.0;
            //int timeParam = (int) Math.ceil(hours * 10);

            
            String message = String.format("%s.%03d.00\r\n", imei, Integer.parseInt(order.getPrepayAmount().toString()));

            // 发送消息，使用IMEI作为主题
            mqttServerService.sendToDevice(imei, message);
            log.info("充电启动指令已发送：topic={}, message={}, 实际充电时长={}分钟", imei, message, chargingMinutes);

            // 🔧 新增：启动重发任务（仅2行代码）
//            simpleChargingRetryService.startRetryTask(order.getOrderId(), imei, chargingMinutes);
//            log.info("重发任务已启动：orderId={}", order.getOrderId());


        } catch (Exception e) {
            log.error("发送充电启动指令失败: orderId={}, eleCode={}",
                    order.getOrderId(), order.getEleCode(), e);
        }
    }

    /**
     * 根据充电桩编码获取IMEI（保持原有行为）
     *
     * @param eleCode 电桩编码
     * @return IMEI或eleCode
     */
    public String getDeviceImei(String eleCode) {
        try {
            // 保持原有逻辑：返回eleCode（实际是ICCID）
            String sql = "SELECT imei FROM charging_pile WHERE ele_code = ? LIMIT 1";
            String result = jct.queryForObject(sql, String.class, eleCode);
            
            if (result != null) {
                log.info("找到设备: imei={}", result);
                return result; // 返回eleCode作为设备标识
            } else {
                log.warn("未找到设备: imei={}", eleCode);
                return eleCode;
            }
        } catch (Exception e) {
            log.error("查询设备失败: imei={}, 使用imei作为fallback", eleCode, e);
            return eleCode; // 出错时直接返回eleCode
        }
    }

    /**
     * 根据充电桩编码获取真实的IMEI字段
     *
     * @param eleCode 电桩编码
     * @return 真实的IMEI
     */
    private String getDeviceRealImei(String eleCode) {
        try {
            // 查询真实的IMEI字段
            String sql = "SELECT imei FROM charging_pile WHERE ele_code = ? LIMIT 1";
            String imei = jct.queryForObject(sql, String.class, eleCode);
            
            if (imei != null && !imei.isEmpty()) {
                log.info("找到设备真实IMEI: eleCode={}, imei={}", eleCode, imei);
                return imei;
            } else {
                log.warn("未找到设备真实IMEI: eleCode={}, 使用eleCode作为fallback", eleCode);
                return eleCode; // fallback到eleCode
            }
        } catch (Exception e) {
            log.error("查询设备真实IMEI失败: eleCode={}, 使用eleCode作为fallback", eleCode, e);
            return eleCode; // 出错时直接返回eleCode
        }
    }

    /**
     * 发送支付成功短信
     * TODO 待完善
     *
     * @param order 订单信息
     */
    private void sendPaymentSuccessSms(OrderEntity order) {
        log.info("暂不发送手机短信");
//        try {
////            // 从订单中获取用户手机号
////            String userPhone = order.getUserPhone(); // 需要确保OrderEntity有这个字段
////            if (userPhone == null || userPhone.isEmpty()) {
////                log.warn("订单{}缺少用户手机号，无法发送短信", order.getOrderId());
////                return;
////            }
//
//            // 暂时注释掉短信发送功能
//            /*
//            // 发送支付成功通知短信，而不是验证码
//            send_code sendcode = new send_code();
//            String message = String.format("您的充电订单%s支付成功，金额%.2f元，请及时开始充电。",
//                                         order.getOrderId(), order.getPrepayAmount());
//            sendcode.sendPaymentSuccessMessage(userPhone, message); // 需要实现专门的支付成功短信方法
//            */
//
//            log.info("支付成功短信功能已暂时禁用，订单: {}, 手机号: {}", order.getOrderId(), userPhone);
//        } catch (Exception e) {
//            log.error("发送支付成功短信失败", e);
//        }
    }

    /**
     * 处理充电桩断电事件
     *
     * @param message 包含断电事件信息的JSON对象
     * @return 处理结果
     */
    @PostMapping("/handlePowerOutage")
    public returnBean<Void> handlePowerOutage(@RequestBody JSONObject message) {
        try {
            String Id = message.getString("id");
            String eleCode = message.getString("ele_code");

            log.info("收到断电事件: Id={}, eleCode={}", Id, eleCode);

            // 修改：使用主键ID查询订单
            OrderEntity order = orderService.getOrderById(Long.parseLong(Id));
            if (order == null) {
                return returnBean.error(404, "订单不存在");
            }

            // 添加：设置充电结束时间
            if (order.getEndTime() == null) {
                order.setEndTime(new Date());
                log.info("设置充电结束时间: orderId={}, endTime={}", Id, order.getEndTime());
            }

            // 计算已充电时间和应退款金额
            BigDecimal refundAmount = calculateRefundAmount(order);

            if(refundAmount.compareTo(BigDecimal.ZERO) > 0) {
                // 修复：发起退款时使用业务订单号而不是主键ID
                boolean refundSuccess = paymentService.refund(order.getOrderId(), refundAmount);

                if (refundSuccess) {
                    // 更新订单状态
                    order.setStatus(ChargingOrder.STATUS_REFUNDED);
                    // 🔧 新增：设置退款金额和退款时间
                    order.setRefundAmount(refundAmount);
                    order.setRefundTime(new Date());
                    order.setUpdateDate(new java.sql.Date(System.currentTimeMillis()));
                    orderService.updateOrder(order);

                    // 🔧 关键修复：退款后解绑设备与订单的关系
                    if (eleCode != null && !eleCode.isEmpty()) {
                        deviceOrderService.unbindDevice(eleCode);
                        log.info("退款后解绑设备成功: eleCode={}, orderId={}", eleCode, Id);
                    }

                    // 发送MQTT通知
                    sendRefundNotification(order, refundAmount);

                    log.info("断电退款处理成功: orderId={}, businessOrderId={}, refundAmount={}", Id, order.getOrderId(), refundAmount);
                    return returnBean.success(null);
                } else {
                    log.error("退款失败: orderId={}, businessOrderId={}", Id, order.getOrderId());
                    return returnBean.error(500, "退款失败");
                }
            }else {
                // 更新订单状态
                order.setStatus(ChargingOrder.STATUS_COMPLETED);
                // 🔧 新增：设置退款金额和退款时间
                order.setRefundAmount(refundAmount);
                order.setRefundTime(new Date());
                order.setUpdateDate(new java.sql.Date(System.currentTimeMillis()));
                orderService.updateOrder(order);
                return returnBean.success(null);
            }
        } catch (Exception e) {
            log.error("处理断电退款失败", e);
            return returnBean.error(500, "系统错误: " + e.getMessage());
        }
    }

    /**
     * 计算退款金额
     * 退款规则：
     * 1. 开始充电后，30秒内断电退全款
     * 2. 充电超过设定时间的70%，不退款
     * 3. 充电大于30秒，小于预订时间的70%，按比例部分退款
     *
     * @param order 订单信息
     * @return 退款金额（元为单位）
     */
    private BigDecimal calculateRefundAmount(OrderEntity order) {
        try {
            // 获取充电开始时间
            Date startTime = order.getStartTime();
            if (startTime == null) {
                log.warn("订单没有开始时间记录，将全额退款: orderId={}", order.getOrderId());
                // 已经是元为单位，直接返回
                return order.getPrepayAmount();
            }

            // 计算已充电时间（秒）
            long chargingTimeInSeconds = (System.currentTimeMillis() - startTime.getTime()) / 1000;

            // 获取预设充电时间（分钟）
            int plannedTimeInMinutes = order.getChargingMinutes() != null ?
                    order.getChargingMinutes() : 60; // 默认1小时

            // 转换为秒
            long plannedTimeInSeconds = plannedTimeInMinutes * 60;

            // 获取预付金额（已经是元为单位，无需转换）
            BigDecimal prepayAmountInYuan = order.getPrepayAmount();
            if (prepayAmountInYuan == null) {
                log.warn("订单没有预付金额记录，无法计算退款: orderId={}", order.getOrderId());
                return BigDecimal.ZERO;
            }

            // 退款规则1：30秒内断电，全额退款
            if (chargingTimeInSeconds <= 30) {
                log.info("充电时间<=30秒，全额退款: orderId={}, chargingTime={}秒, refundAmount={}元",
                        order.getOrderId(), chargingTimeInSeconds, prepayAmountInYuan);
                return prepayAmountInYuan;
            }

            // 退款规则2：充电超过70%，不退款
            if (chargingTimeInSeconds >= plannedTimeInSeconds * 0.7) {
                log.info("充电时间>=70%，不退款: orderId={}, chargingTime={}秒, plannedTime={}秒",
                        order.getOrderId(), chargingTimeInSeconds, plannedTimeInSeconds);
                return BigDecimal.ZERO;
            }

            // 退款规则3：按比例退款
            BigDecimal remainingTimeRatio = BigDecimal.valueOf(plannedTimeInSeconds - chargingTimeInSeconds)
                    .divide(BigDecimal.valueOf(plannedTimeInSeconds), 4, BigDecimal.ROUND_HALF_UP);
            BigDecimal refundAmount = prepayAmountInYuan.multiply(remainingTimeRatio);

            log.info("按比例退款: orderId={}, chargingTime={}秒, plannedTime={}秒, remainingRatio={}%, refundAmount={}元",
                    order.getOrderId(), chargingTimeInSeconds, plannedTimeInSeconds,
                    remainingTimeRatio.multiply(BigDecimal.valueOf(100)).setScale(2),
                    refundAmount.setScale(2, BigDecimal.ROUND_HALF_UP));

            return refundAmount.setScale(2, BigDecimal.ROUND_HALF_UP);
        } catch (Exception e) {
            log.error("计算退款金额失败", e);
            return BigDecimal.ZERO;
        }
    }

    /**
     * 发送退款通知
     * TODO 待完善
     *
     * @param order        订单信息
     * @param refundAmount 退款金额
     */
    private void sendRefundNotification(OrderEntity order, BigDecimal refundAmount) {
        try {
            JSONObject mqttMsg = new JSONObject();
            mqttMsg.put("event_type", "charging_refund");
            mqttMsg.put("order_id", order.getOrderId());
            mqttMsg.put("ele_code", order.getEleCode());
            mqttMsg.put("refund_amount", refundAmount);
            mqttMsg.put("user_id", order.getUserId());

            // 使用用户ID后4位作为主题后缀
            String clientSuffix = order.getUserId().substring(order.getUserId().length() - 4);
            String topic = "notify/charging/" + clientSuffix;

            mqttServerService.sendToDevice(topic, mqttMsg.toJSONString());
            log.info("退款通知已发送: topic={}, message={}", topic, mqttMsg);
        } catch (Exception e) {
            log.error("发送退款通知失败: orderId={}", order.getOrderId(), e);
        }
    }
    @GetMapping("/getAlipayOpenId")
    public String getAlipayOpenId(@RequestParam String auth_code) {
        try {
            log.info("收到获取支付宝OpenID请求，授权码: {}", auth_code);
            
            if (auth_code == null || auth_code.trim().isEmpty()) {
                log.error("授权码参数为空");
                return "授权码不能为空";
            }
            
            // 直接调用支付宝服务获取用户ID，作为openid返回
            String openId = aliPayService.getUserId(auth_code);
            if (openId != null && !openId.trim().isEmpty()) {
                log.info("成功获取支付宝OpenID: {}", openId);
                return openId;
            } else {
                log.error("获取支付宝OpenID失败，返回null或空字符串");
                return "获取OpenID失败，请检查授权码是否有效";
            }
        } catch (Exception e) {
            log.error("获取支付宝OpenID异常", e);
            return "系统异常：" + e.getMessage();
        }
    }


    @PostMapping("/by_ele_code")
    public returnBean<String> updateOrderStatus(@RequestParam String ele_code) {
        // 实现更新订单状态逻辑
        try {
            // 先检查订单是否存在
            String selectSql = "SELECT id FROM charging_order WHERE ele_code = "+ ele_code +" AND status in (1,2)";
            List<String> order = jct.queryForList(selectSql, String.class);
            if(order.size() == 0) {
                return returnBean.success(null);
            }else {
                return returnBean.error(-1,"有正在充电的订单");
            }
        } catch (Exception e) {
            String errorMessage = "订单状态更新失败: " + e.getMessage().replace("\\", "\\\\").replace("'", "\\'");
            return returnBean.error(500, errorMessage);
        }
    }




    // 添加GET接口作为备选，完全通过URL参数传递
    @GetMapping("/alipayCreateOrderGet")
    public void alipayCreateOrderGet(
        @RequestParam String auth_code,
        @RequestParam String ele_code,
        @RequestParam BigDecimal prepayAmount,
        @RequestParam(required = false, defaultValue = "DEFAULT") String region_code,
        HttpServletRequest request,
        HttpServletResponse response) throws IOException {
        
        // 构建bean_order对象
        bean_order param = new bean_order();
        param.setEleCode(ele_code);
        param.setPrepayAmount(prepayAmount);
        param.setRegionCode(region_code);
        // 从auth_code获取用户ID（这里需要实现获取逻辑）
        param.setUserId("test_user_id"); // 临时使用测试用户ID
        
        // 调用统一的POST方法逻辑
        RespObj<String> result = alipayCreateOrder(param);
        
        // 处理返回结果
        if (result.getCode() == 200 && result.getData() != null) {
            // 直接写入HTML支付表单到响应
            response.setContentType("text/html;charset=UTF-8");
            response.getWriter().write(result.getData());
            response.getWriter().flush();
        } else {
            // 处理错误情况
            response.setContentType("text/html;charset=UTF-8");
            response.getWriter().write("<script>alert('支付创建失败: " + result.getMessage() + "'); history.back();</script>");
            response.getWriter().flush();
        }
    }

    /**
     * 从支付宝HTML表单中提取支付URL
     * @param paymentForm HTML表单字符串
     * @return 支付URL
     */
    private String extractPaymentUrl(String paymentForm) {
        try {
            // 从HTML表单中提取action属性的URL
            String actionPattern = "action=\"([^\"]+)\"";
            java.util.regex.Pattern pattern = java.util.regex.Pattern.compile(actionPattern);
            java.util.regex.Matcher matcher = pattern.matcher(paymentForm);
            
            if (matcher.find()) {
                String actionUrl = matcher.group(1);
                log.info("提取到支付URL: {}", actionUrl);
                return actionUrl;
            } else {
                log.warn("无法从支付表单中提取URL，返回默认值");
                return "https://openapi.alipay.com/gateway.do";
            }
        } catch (Exception e) {
            log.error("提取支付URL失败", e);
            return "https://openapi.alipay.com/gateway.do";
        }
    }



    /**
     * 获取统计
     *
     * @return
     */
    @PostMapping("/getOrderStatisticsByMonth")
    public returnBean<List<StatisticsByMonth>> getOrderStatisticsByMonth(@RequestParam(value = "param", required = false) String eleCode, @RequestParam String startDate, @RequestParam String endDate) {
        try {
            List<StatisticsByMonth> list = chargingOrderService.getOrderStatisticsByMonth(eleCode, startDate, endDate);
            return returnBean.success(list);
        } catch (Exception e) {
            return returnBean.error(-1,"查询统计结果失败");
        }
    }



    @PostMapping("/getOrderStatisticsByDay")
    public returnBean<List<StatisticsByDay>> getOrderStatisticsByDay(@RequestParam(value = "param", required = false) String eleCode, @RequestParam String Date) {
        try {
            List<StatisticsByDay> list = chargingOrderService.getOrderStatisticsByDay(eleCode,Date);
            return returnBean.success(list);
        } catch (Exception e) {
            return returnBean.error(-1,"查询统计结果失败");
        }
    }
}